package ext.tianma.workflow;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

import wt.clients.vc.CheckInOutTaskLogic;
import wt.fc.ObjectIdentifier;
import wt.fc.ObjectReference;
import wt.fc.Persistable;
import wt.fc.PersistenceHelper;
import wt.fc.QueryResult;
import wt.fc.WTObject;
import wt.fc.collections.WTCollection;
import wt.folder.CabinetBased;
import wt.folder.FolderHelper;
import wt.inf.container.WTContainerRef;
import wt.lifecycle.LifeCycleException;
import wt.lifecycle.LifeCycleHelper;
import wt.lifecycle.LifeCycleManaged;
import wt.lifecycle.State;
import wt.method.RemoteAccess;
import wt.org.WTPrincipal;
import wt.org.WTPrincipalReference;
import wt.org.WTUser;
import wt.part.WTPart;
import wt.project.Role;
import wt.query.ClassAttribute;
import wt.query.OrderBy;
import wt.query.QueryException;
import wt.query.QuerySpec;
import wt.query.SearchCondition;
import wt.session.SessionHelper;
import wt.session.SessionServerHelper;
import wt.team.Team;
import wt.team.TeamHelper;
import wt.util.WTException;
import wt.util.WTProperties;
import wt.util.WTPropertyVetoException;
import wt.vc.wip.Workable;
import wt.workflow.definer.WfContainerTemplate;
import wt.workflow.definer.WfDefinerHelper;
import wt.workflow.definer.WfProcessTemplate;
import wt.workflow.definer.WfProcessTemplateMaster;
import wt.workflow.engine.ProcessData;
import wt.workflow.engine.WfActivity;
import wt.workflow.engine.WfBlock;
import wt.workflow.engine.WfConnector;
import wt.workflow.engine.WfEngineHelper;
import wt.workflow.engine.WfEngineServerHelper;
import wt.workflow.engine.WfProcess;
import wt.workflow.engine.WfState;
import wt.workflow.engine.WfVotingEventAudit;
import wt.workflow.work.WfAssignedActivity;
import wt.workflow.work.WorkItem;
import wt.workflow.work.WorkflowHelper;
import ext.generic.erp.query.SupplierInfoIETask;
import ext.generic.integration.sourcing.task.QuerySupplierInfoIETask;
import ext.tianma.part.forms.TMTypeUtil;

/**
 * 流程实用类
 * 
 * @author Kevin Xu
 * 
 */

public class workflowCommands implements RemoteAccess, Serializable {
	public static boolean VERBOSE = false;
	public static WTProperties wtProperties;
	public static String CLASSNAME = "";
	public static String ACADEXTNAME = "dwg";
	public static String CAXAEXTNAME = "exb";
	public static String PROEDRWEXTNAME = "drw";
	public static boolean SUPPLIERVERBOSE = true;

	static {
		CLASSNAME = workflowCommands.class.getName();
		try {
			wtProperties = WTProperties.getLocalProperties();
			VERBOSE = wtProperties.getProperty("ext.tianma.workflow.verbose", false);
			//SUPPLIERVERBOSE = wtProperties.getProperty("ext.tianma.erp.supplierVerbose", false);
		} catch (java.io.IOException ioe) {
			ioe.printStackTrace();
		}
	}

	/**
	 * 判断某一特定对象是否处于检出状态
	 * 
	 * @param wto
	 * @return
	 * @throws WTException
	 * @throws WTPropertyVetoException
	 */
	public static boolean isObjectCheckedOut(WTObject wto) throws WTException, WTPropertyVetoException {
		boolean flag = SessionServerHelper.manager.setAccessEnforced(false);
		try {
			if ((wto instanceof Workable) && (wto instanceof CabinetBased)
					&& (CheckInOutTaskLogic.isCheckedOut((Workable) wto) || FolderHelper.inPersonalCabinet((CabinetBased) wto))) {
				throw new WTException("当前对象处于检出状态，不能完成任务，请检查！");
			} else
				return false;
		} /*catch (Exception e) {
			e.printStackTrace();
		}*/ finally {
			SessionServerHelper.manager.setAccessEnforced(flag);
		}
		//return false;
	}

	public static void processRejectOfWork(Object obj, WTObject pbo) throws WTException {

		/*
		 * //customization NO.1 begin
		 * 
		 * //获取工作流流程 WfProcess process=null; NmOid
		 * nmoid=(NmOid)paramNmCommandBean.getPrimaryOid(); String
		 * oid=(String)nmoid.getOid().toString(); ReferenceFactory rf = new
		 * ReferenceFactory(); WorkItem
		 * item=(WorkItem)rf.getReference(oid).getObject(); Persistable pbo=
		 * item.getPrimaryBusinessObject().getObject(); try { NmOid nmoids =
		 * NmOid.newNmOid(PersistenceHelper.getObjectIdentifier(pbo));
		 * QueryResult qr =
		 * NmWorkflowHelper.service.getRoutingHistoryData(nmoids);
		 * if(qr.hasMoreElements()){ process=(WfProcess)qr.nextElement(); } }
		 * catch (Exception e) { e.printStackTrace(); }
		 */
		//ext.com.workflow.WorkflowUtil.initializeRoleHolderByProcessCreator(self, "", 30);
		WfProcess process = getProcess(obj);
		// 获取用户的投票结果
		WTCollection auditCol = WfEngineHelper.service.getVotingEvents(process, null, null, null);
		Iterator auditEvents = auditCol.persistableIterator();
		while (auditEvents.hasNext()) {
			WfVotingEventAudit audit = (WfVotingEventAudit) auditEvents.next();
			// System.out.println("Transition Expression: User vote = " +
			// audit.getEventList().toString());
			// 此处判断一下用户的投票结果是否是驳回
			System.out.println(">>>>>>>>>audit.getEventList().toString():" + audit.getEventList().toString());
			if ("[驳回]".equals(audit.getEventList().toString())) {

				WfState wfState = process.getState();
				System.out.println("PROCESS STATE = " + wfState.toString());
				WfAssignedActivity wfAssignedActivity = null;
				if (wfState.toString().equals("OPEN_RUNNING")) {
					// 搜索工作流流程下的所有活动
					QuerySpec wfAssignedActivityQuerySpec = new QuerySpec(WfAssignedActivity.class);
					SearchCondition sc = new SearchCondition(WfAssignedActivity.class, "state", SearchCondition.EQUAL, "OPEN_RUNNING");
					wfAssignedActivityQuerySpec.appendSearchCondition(sc);
					sc = new SearchCondition(WfAssignedActivity.class, "parentProcessRef.key", "=",
							PersistenceHelper.getObjectIdentifier(process));
					wfAssignedActivityQuerySpec.appendAnd();
					wfAssignedActivityQuerySpec.appendSearchCondition(sc);
					QueryResult qr = PersistenceHelper.manager.find(wfAssignedActivityQuerySpec);
					while (qr.hasMoreElements()) {
						wfAssignedActivity = (WfAssignedActivity) qr.nextElement();
						// 获得活动的名字
						System.out.println("wfactivityName=" + wfAssignedActivity.getName());
						try {
							Team team = TeamHelper.service.getTeam(process);
							if (team == null)
								return;
							// 得到活动参与者DESIGNER下的用户
							Role role = Role.toRole("Signer");
							Enumeration participants = team.getPrincipalTarget(role);
							System.out.println(">>>>>>>>>>>>>>>>participants:" + participants.hasMoreElements());
							while (participants.hasMoreElements()) {
								WTPrincipalReference principalRef = (WTPrincipalReference) participants.nextElement();
								if (principalRef == null || principalRef.isDisabled())
									continue;
								WTPrincipal principal = principalRef.getPrincipal();
								System.out.println(">>>>>>>>>>>>>>>>>>>>>>user:" + principal.getName());
								WTPrincipal loginPrincipal = SessionHelper.manager.getPrincipal();
								if (!(loginPrincipal.getName().equals(principal.getName()))) {
									// 指定pbo和用户的任务
									Enumeration userWorkItems = WorkflowHelper.service.getWorkItems((WTObject) pbo, principal);
									while (userWorkItems.hasMoreElements()) {
										WorkItem workItem = (WorkItem) userWorkItems.nextElement();
										// 筛选未完成
										if (!workItem.isComplete()) {
											WfActivity currentActivityName = (WfActivity) workItem.getSource().getObject();
											System.out.println(">>>>>>>>>>>>>>>>>>wfActivity name=" + currentActivityName.getName());
											// 活动名相同
											if (currentActivityName.getName().equals("原材料审核(BOM工程师)")) {
												// System.out.println("完成指定pbo("
												// + pbo + ")里指定用户(" +
												// pricipal.getName() +
												// ")的指定活动名(" + activityName +
												// ")的任务");
												WTPrincipalReference userref = workItem.getOwnership().getOwner();
												System.out.println(">>>>>>>>>>>>>>>>>>>>>>>>>>userref:" + userref.getName());
												System.out.println(">>>>>>>>>>>>>>>>>>>>>>>>>>userref.getPrincipal().getName():"
														+ userref.getPrincipal().getName());
												// 任务执行人和指定用户相同o
												if (userref.getName().equals(principal.getName())) {
													System.out.println(">>>>>>>>>>>>>>>>>>>>.true ");
													WorkflowHelper.service.workComplete(workItem, userref, null);
												}
											}
										}
									}

								}
							}
						} catch (WTException e) {
							e.printStackTrace();
						}

					}

				}

			}
			audit.getEventList().clear();
			break;
		}

	}

	/**
	 * 将流程中的SELF 转化为流程对象
	 * 
	 * @param obj
	 *            流程对象
	 * @return
	 */
	public static WfProcess getProcess(Object obj) {
		if (obj == null) {
			return null;
		}
		try {
			Persistable persistable = null;
			if (obj instanceof Persistable) {
				persistable = (Persistable) obj;
			} else if (obj instanceof ObjectIdentifier) {
				persistable = PersistenceHelper.manager.refresh((ObjectIdentifier) obj);
			} else if (obj instanceof ObjectReference) {
				persistable = ((ObjectReference) obj).getObject();
			}
			if (persistable == null) {
				return null;
			}
			if (persistable instanceof WorkItem) {
				persistable = ((WorkItem) persistable).getSource().getObject();
			}
			if (persistable instanceof WfActivity) {
				persistable = ((WfActivity) persistable).getParentProcess();
			}
			if (persistable instanceof WfConnector) {
				persistable = ((WfConnector) persistable).getParentProcessRef().getObject();
			}
			if (persistable instanceof WfBlock) {
				persistable = ((WfBlock) persistable).getParentProcess();
			}
			if (persistable instanceof WfProcess) {
				return (WfProcess) persistable;
			}
		} catch (Exception e) {
			e.getMessage();
		}
		return null;
	}

	/**
	 * 获取币种
	 * 
	 * @return 币种的集合
	 */
	public static List getCurrencyList() {
		List list = new ArrayList();
		list.add("");
		list.add("人民币（CNY）");
		list.add("美圆（USD）");
		list.add("日圆（JPY）");
		return list;

	}

	/**
	 * 获取供应商信息
	 * 
	 * @return 供应商集合
	 */
	public static Map<String, String> getSupplierFromERP(String name) {
		Map<String,String> map = new LinkedHashMap<String,String>() ;
		System.out.println("Debug  要查寻的参数为："+name);

		if(!SUPPLIERVERBOSE)
		{
			map = getSupplier();
		}
		else
		{
			map = SupplierInfoIETask.queryLikeName(name);
		}
		Iterator it = map.keySet().iterator();
		while(it.hasNext())
		{
			String key = (String) it.next();
			String value  = map.get(key);
		}
		return map;
	}
	
	/**
	 * 获取模具供应商信息
	 * 
	 * @return 供应商集合
	 */
	public static Map<String, String> getDieSupplierFromERP(String name) {
		Map<String,String> map = new LinkedHashMap<String,String>() ;
		System.out.println("Debug  要查寻的参数为："+name);

		if(!SUPPLIERVERBOSE)
		{
			map = getSupplier();
		}
		else
		{
			map = QuerySupplierInfoIETask.queryLikeName(name);
		}
		
		return map;
	}

	/**
	 * 获取供应商信息
	 * 
	 * @return 供应商集合
	 */
	public static Map<String, String> getSupplier() {
		Map<String,String> map = new LinkedHashMap<String,String>() ;
		map.put("001", "北京天马");
		map.put("002", "上海天马");


		return map;

	}

	/**
	 * 启动版本进阶流程
	 * @param pbo 主要业务对象
	 * @throws QueryException
	 * @throws WTException
	 * @throws WTPropertyVetoException
	 */
	public static void startVersionPromoteWorkFlow(WTPart pbo) throws QueryException, WTException, WTPropertyVetoException {
		//try {
			WTContainerRef wtcontainerref = pbo.getContainerReference();
			QuerySpec querysearch = null;
			QueryResult queryresult = null;
			querysearch = new QuerySpec(WfProcessTemplate.class);
			SearchCondition sc = new SearchCondition(WfProcessTemplate.class, "name", SearchCondition.EQUAL, "版本进阶物料编码申请流程");
			querysearch.appendWhere(sc);
			OrderBy orderby = new OrderBy(new ClassAttribute(WfProcessTemplate.class, "thePersistInfo.createStamp"), true); // true为降序，false为升序
			querysearch.appendOrderBy(orderby, 0);

			queryresult = PersistenceHelper.manager.find(querysearch);
			WfProcessTemplate wfprocesstemplate = null;
			
			if (queryresult.hasMoreElements()) {
				wfprocesstemplate = (WfProcessTemplate) queryresult.nextElement();
				System.out.println("Debug  版本进阶  获取到的流程模板名称："+wfprocesstemplate.getName());
				WfContainerTemplate wfcontainertemplate = WfDefinerHelper.service
						.getLatestIteration((WfProcessTemplateMaster) wfprocesstemplate.getMaster());
				WTPrincipal wtprincipal = SessionHelper.manager.getPrincipal();
				String processName = "版本进阶物料编码申请流程_"+pbo.getNumber();
				String objstate= ((LifeCycleManaged)pbo).getLifeCycleState().toString();
				String creator = ((WTUser)wtprincipal).getFullName();
				System.out.println("Debug  版本进阶  启动流程的用户名称："+wtprincipal.getName());
				WTPrincipalReference wtprincipalreference = WTPrincipalReference.newWTPrincipalReference(wtprincipal);

				boolean flag = SessionServerHelper.manager.setAccessEnforced(false);
				try {
					
					WfProcess wfprocess = WfEngineHelper.service.createProcess(wfprocesstemplate, pbo.getLifeCycleTemplate(),pbo.getContainerReference());
					WfEngineServerHelper.service.setPrimaryBusinessObject(wfprocess,pbo);
					wfprocess.setName(processName);
		    		ProcessData processdata = wfprocess.getContext();
		    		//processdata.setValue("objstate", objstate);
		    		//processdata.setValue("creator", creator);
		    		wfprocess.setCreator(wtprincipalreference);
		    		wfprocess = (WfProcess)PersistenceHelper.manager.save(wfprocess);	
		    		wfprocess.start(processdata, true, pbo.getContainerReference());
					
		    		//WfEngineHelper.service.getAssociatedProcesses((LifeCycleManaged)pbo,WfState.);

					
					
					
/*					WfProcess wfprocess = WfProcess.newWfProcess(wtcontainerref);
					wfprocess.setHasContents(true);
					System.out.println("Debug  版本进阶  启动流程的流程名称："+wfprocess.getName());
					 
					// wfprocess.setProcessAttributes(wfcontainertemplate, wtprincipalreference, pbo, wtcontainerref);

					WfTemplateObjectReference ref = WfTemplateObjectReference.newWfTemplateObjectReference(wfcontainertemplate);
					System.out.println("1111111111111");
					wfprocess.setTemplate(ref);
					System.out.println("222222222");
					
					ReferenceFactory rf = new ReferenceFactory();
			         WTReference wtrf = rf.getReference(pbo.toString());
			         String oid = rf.getReferenceString(wtrf);

					wfprocess.setBusinessObjReference(oid);
					System.out.println("333333333");
					wfprocess.setContainerReference(wtcontainerref);
					System.out.println("444444444");
					wfprocess.setCreator(wtprincipalreference);
					System.out.println("55555555555");
					wfprocess = (WfProcess) PersistenceHelper.manager.save(wfprocess);
					System.out.println("6666666666666");
					ProcessData processdata = wfprocess.getContext();
					System.out.println("777777777777777777");
					if(null==processdata)
					{
						System.out.println("Debug  版本进阶  启动流程的流程   processdata is null");
					}
					else
					{
						System.out.println("Debug  版本进阶  启动流程的流程   processdata not null");
					}
					processdata.setValue("primaryBusinessObject", pbo);
					//wfprocess.setPrimaryBusinessObject(processdata);
					System.out.println("88888888888888888");
					wfprocess.setContext(processdata);
					if(null==wfprocess)
					{
						System.out.println(" wfprocess is null 1");
					}
					else
					{
						System.out.println(" wfprocess is  not null 1");
					}
					wfprocess = (WfProcess) PersistenceHelper.manager.save(wfprocess);
					if(null==wfprocess)
					{
						System.out.println(" wfprocess is null 2");
					}
					//wfprocess.changeState(WfTransition.START, true);
					if(null==WfTransition.START)
					{
						System.out.println(" ttttttttttttttttttttt");
					}
					
					
					wfprocess.changeState(WfTransition.START);
					System.out.println("99999999999999999");
					Team team = (Team) ((TeamReference) ((TeamManaged) wfprocess).getTeamId()).getObject();
					System.out.println("aaaaaaaaaaaaaaaaaa");
					team = (Team) PersistenceHelper.manager.refresh(team);
					System.out.println("bbbbbbbbbbbbbbbbbb");
					ext.tianma.access.AccessUtil.setObjectAccess(team, wtprincipal, AccessPermission.MODIFY);
					System.out.println("ccccccccccccccccc");*/
				} 
				//catch (Exception e) {
					//throw new WTException(e.toString());
			//	} 
				finally {
					SessionServerHelper.manager.setAccessEnforced(flag);
				}
			}

		//} catch (Exception e) {
			// TODO Auto-generated catch block
			//throw new WTException(e.toString());
		//}
	}
	/**
	 * 设置PBO生命周期状态
	 * @param pbo
	 * @throws LifeCycleException
	 * @throws WTException
	 */
	public static void setStateOfPBO1(WTObject pbo) throws LifeCycleException, WTException
	{
		if(pbo instanceof WTObject)
		{
			boolean flag = SessionServerHelper.manager.setAccessEnforced(false);
			try{
				WTPart part = (WTPart) pbo;
				if( TMTypeUtil.isFinishedGood( part ) )
				{
					part= (WTPart)LifeCycleHelper.service.setLifeCycleState(part, State.INWORK);
				}
				else
				{
					State state = State.toState("NewPartReview");
					part= (WTPart)LifeCycleHelper.service.setLifeCycleState(part, state);
				}
			}finally{
				SessionServerHelper.manager.setAccessEnforced( flag );
			}
			
		}
		else
		{
			System.out.println("版本进阶流程的PBO不是部件类型请检查！");
		}
	}
	
	/**
	 * 设置PBO生命周期状态
	 * @param pbo
	 * @throws LifeCycleException
	 * @throws WTException
	 */
	public static void setStateOfPBO2(WTObject pbo) throws LifeCycleException, WTException
	{
		if(pbo instanceof WTObject)
		{
			WTPart part = (WTPart) pbo;
			boolean flag = SessionServerHelper.manager.setAccessEnforced(false);
			try{
				if( TMTypeUtil.isFinishedGood( part ) ){
					State state = State.toState("REWORK");
					part= (WTPart)LifeCycleHelper.service.setLifeCycleState(part, state);
				}
				else{
					State state = State.toState("NewPartModify");
					part= (WTPart)LifeCycleHelper.service.setLifeCycleState(part, state);
				}
			}finally{
				SessionServerHelper.manager.setAccessEnforced( flag );
			}	
		}
		else
		{
			System.out.println("版本进阶流程的PBO不是部件类型请检查！");
		}
	}
	
	
	public static void startRAWTransitFactoryWorkFlow(WTPart pbo) throws QueryException, WTException, WTPropertyVetoException 
	{
		WTContainerRef wtcontainerref = pbo.getContainerReference();
		QuerySpec querysearch=null;
		QueryResult queryresult=null;
		querysearch= new QuerySpec(WfProcessTemplate.class);
		SearchCondition sc = new SearchCondition(WfProcessTemplate.class, "name", SearchCondition.EQUAL, "二供物料编码申请流程");
		querysearch.appendWhere(sc);
		OrderBy orderby = new OrderBy(new ClassAttribute(WfProcessTemplate.class, "thePersistInfo.createStamp"), true);	//true为降序，false为升序
		querysearch.appendOrderBy(orderby, 0);
		
		queryresult= PersistenceHelper.manager.find(querysearch);	
		WfProcessTemplate wfprocesstemplate = null;
		if(queryresult.hasMoreElements()){
			wfprocesstemplate = (WfProcessTemplate)queryresult.nextElement();
			WfContainerTemplate wfcontainertemplate = WfDefinerHelper.service.getLatestIteration((WfProcessTemplateMaster)wfprocesstemplate.getMaster());
			WTPrincipal wtprincipal = SessionHelper.manager.getPrincipal();
			WTPrincipalReference wtprincipalreference = WTPrincipalReference.newWTPrincipalReference(wtprincipal);
			String processName = "二供物料编码申请流程_"+pbo.getNumber();
			String objstate= ((LifeCycleManaged)pbo).getLifeCycleState().toString();
			String creator = ((WTUser)wtprincipal).getFullName();
			boolean flag = SessionServerHelper.manager.setAccessEnforced(false);
			try{
				WfProcess wfprocess = WfEngineHelper.service.createProcess(wfprocesstemplate, pbo.getLifeCycleTemplate(),pbo.getContainerReference());
				WfEngineServerHelper.service.setPrimaryBusinessObject(wfprocess,pbo);
				wfprocess.setName(processName);
	    		ProcessData processdata = wfprocess.getContext();
	    		//processdata.setValue("objstate", objstate);
	    		//processdata.setValue("creator", creator);
	    		wfprocess.setCreator(wtprincipalreference);
	    		wfprocess = (WfProcess)PersistenceHelper.manager.save(wfprocess);	
	    		wfprocess.start(processdata, true, pbo.getContainerReference());
			}
			catch(Exception e)
			{
				e.printStackTrace();
			}
			finally
			{
				SessionServerHelper.manager.setAccessEnforced(flag);
			}
		}

	}
}
